// import axios from 'axios'
import { MessageBox, Message } from 'element-ui'
import store from '@/store'
import { getToken } from '@/utils/auth'
import Axios from 'axios'
import Vue from 'vue'

import Oauth from 'axios-oauth-client'
import { removeToken } from './auth'
// create an axios instance
const service = Axios.create({
  baseURL: process.env.VUE_APP_BASE_API, // url = base url + request url
  // withCredentials: true, // send cookies when cross-domain requests
  timeout: 5000 // request timeout
})

// request interceptor
service.interceptors.request.use(
  config => {
    // do something before request is sent

    if (store.getters.token) {
      // let each request carry token
      // ['X-Token'] is a custom headers key
      // please modify it according to the actual situation
      config.headers['X-Token'] = getToken()
    }
    return config
  },
  error => {
    // do something with request error
    console.log(error) // for debug
    return Promise.reject(error)
  }
)

// response interceptor
service.interceptors.response.use(
  /**
   * If you want to get http information such as headers or status
   * Please return  response => response
  */

  /**
   * Determine the request status by custom code
   * Here is just an example
   * You can also judge the status by HTTP Status Code
   */
  response => {
    const res = response.data
    console.log(res, response.data, '---------------------------------')
    // if the custom code is not 20000, it is judged as an error.
    if (res.code !== 200) {
      Message({
        message: res.message || 'Error',
        type: 'error',
        duration: 5 * 1000
      })

      // 50008: Illegal token; 50012: Other clients logged in; 50014: Token expired;
      if (res.code === 207||res.code === 50008 || res.code === 50012 || res.code === 50014) {
        // to re-login
        MessageBox.confirm('登录已失效，请重新登录', '重新登录', {
          confirmButtonText: '确认',
          type: 'warning'
        }).then(() => {
          store.dispatch('user/resetToken').then(() => {
            this.router.push('/login')
          })
        })
      }
      return Promise.reject(new Error(res.msg || 'Error'))
    } else {
      return res
    }
  },
  error => {
    console.log('err' + error) // for debug
    Message({
      message: error.message,
      type: 'error',
      duration: 5 * 1000
    })
    return Promise.reject(error)
  }
)

export default service

/**
 * 请求拦截器：设置请求token
 * @author
 * @date 2020-11-06 13:12
 * @param
 **/
function requestTokenInterceptor(config) {
  // config.headers[linkToken.authKey] = linkToken.getLocalToken();
  return config
}

/**
 * 请求错误拦截器
 * @author
 * @date 2020-11-06 13:11
 **/
function requestErrorInterceptor(error) {
  // linkLog.error(error);// 日志
  return Promise.reject(error)
}

/**
 * 响应成功拦截器
 * @author
 * @date 2020-11-06 13:11
 * @param
 **/
function responseSuccessInterceptor(response) {
  // linkToken.refreshExpires(); // 更新token过期时间
  return response
}

/**
 * 响应失败拦截器
 * @param error
 * @returns {Promise<never>}
 */
function responseErrorInterceptor(error) {

  console.log(error)
  if (error.response) {
    console.log(error.response.data.code)
    if (error.response.data.code === 207) {
      removeToken()
    } else if (error.response.data.code === 301) {
      MessageBox.alert('您没有权限访问该接口！', '错误')
    }
  } else {
    console.log('网络异常！', error)
  }
  // linkLog.error(error);// 日志
  return Promise.reject(error)
}

/**
 * 表单axios服务，会将参数格式化为表单格式，application/x-www-form-urlencoded
 * @author
 * @date 2020-11-06 13:10
 * @param
 **/
const axios1 = window.axios1 = Vue.prototype.$http1 = Axios.create({
  baseURL: process.env.VUE_APP_BASE_API,
  headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
  withCredentials: false,
  crossDomain: true,
  transformRequest: [
    function(data) {
      var ret = ''
      for (var it in data) {
        ret += encodeURIComponent(it) + '=' + encodeURIComponent(data[it]) + '&'
      }
      return ret
    }

  ]
})
axios1.defaults.withCredentials = false
axios1.defaults.crossDomain = true
axios1.interceptors.request.use(requestTokenInterceptor, requestErrorInterceptor)
axios1.interceptors.response.use(responseSuccessInterceptor, responseErrorInterceptor)

const pureAxios = Axios.create({})
pureAxios.defaults.baseURL = process.env.VUE_APP_BASE_API
pureAxios.defaults.withCredentials = false
pureAxios.defaults.crossDomain = true

/**
 * 基础axios服务，参数默认为json格式，application/json
 * @author
 * @date 2020-11-06 13:10
 **/
const axios = window.axios = Axios
axios.defaults.baseURL = process.env.VUE_APP_BASE_API
axios.defaults.withCredentials = false
axios.defaults.crossDomain = true
axios.interceptors.request.use(requestTokenInterceptor, requestErrorInterceptor)
axios.interceptors.response.use(responseSuccessInterceptor, responseErrorInterceptor)

/**
 * oauth 登录封装
 * @date 2021-05-10
 */
const oauthHttp = Vue.prototype.$oauth = {

  oauthRequst(url, param) {
    this.oauthPost(url, param)
  },

  async oauthPost(url, param) {
    const newParam = Object.assign(param, {
      url: process.env.VUE_APP_BASE_API + url,
      grant_type: 'password',
      client_secret: '123456'
    })
    const loginRes = await Oauth.client(Axios.create(), newParam)
    const result = await loginRes()
    return result
  }
}

const http = Vue.prototype.$http = {
  variable: {
    axios,
    axios1
  },
  /**
   * 发送get请求
   * @author
   * @date 2020/11/08
   * @param url 请求地址
   * @param param 请求参数
   * @param formatFormParam 为true使用axios1表单axios服务，为false使用基础axios服务
   */
  async get(url, param, formatFormParam = false) {
    return this.request2(url, param, formatFormParam, 'get')
  },

  /**
   * 发送post请求
   * @author
   * @date 2020-11-06 13:07
   * @param url 请求地址
   * @param param 请求参数
   * @param formatFormParam 为true使用axios1表单axios服务，为false使用基础axios服务
   **/
  async post(url, param, formatFormParam = false) {
    return this.request(url, param, formatFormParam, 'post')
  },
  /**
   * 发送del请求
   * @author
   * @date 2020-11-06 13:07
   * @param url 请求地址
   * @param param 请求参数
   * @param formatFormParam 为true使用axios1表单axios服务，为false使用基础axios服务
   **/
  async delete(url, param, formatFormParam = false) {
    return this.requestDel(url, param, formatFormParam, 'post')
  },

  /**
   * 发送del请求
   * @author
   * @date 2020-11-06 13:07
   * @param url 请求地址
   * @param param 请求参数
   * @param formatFormParam 为true使用axios1表单axios服务，为false使用基础axios服务
   **/
  async put(url, param, formatFormParam = false) {
    return this.requestPul(url, param, formatFormParam, 'post')
  },

  /**
   * 发送请求
   * @author
   * @date 2020-11-06 13:09
   * @param url 请求地址
   * @param param 请求参数
   * @param formatFormParam 为true使用axios1表单axios服务，为false使用基础axios服务,为true会自动格式化参数
   * @param requestMethod 请求方法
   **/
  async requestPul(url, params, formatFormParam = false, requestMethod) {
    requestMethod = requestMethod
    params = params || {}
    const token = getToken()
    const { data } = await axios.put(url, params,
      {
        headers: {
          Accept: 'application/json, text/plain, */*',
          Authorization: 'Bearer ' + token
        },
        crossDomain: true,
        withCredentials: false }

    )
    if (data.code == 207) {
      removeToken()
      return
      // top.location.href = top.appCtx.publicPath + process.env.LogoutPage;
    } else if(data.code == 301) {
      MessageBox.alert('您没有权限访问该接口！', '错误')
      return;
    }
    return data
  },

  /**
   * 发送请求
   * @author
   * @date 2020-11-06 13:09
   * @param url 请求地址
   * @param param 请求参数
   * @param formatFormParam 为true使用axios1表单axios服务，为false使用基础axios服务,为true会自动格式化参数
   * @param requestMethod 请求方法
   **/
  async requestDel(url, param, formatFormParam = false, requestMethod = 'post') {
    requestMethod = requestMethod || 'post'
    param = param || {}
    const token = getToken()
    const { data } = await axios.delete(url, { params: param,
      headers: {
        Accept: 'application/json, text/plain, */*',
        Authorization: 'Bearer ' + token
      },
      crossDomain: true,
      withCredentials: false }
    )
    if (data.code == 207) {
      removeToken()
      return
      // top.location.href = top.appCtx.publicPath + process.env.LogoutPage;
    } else if(data.code == 301) {
      MessageBox.alert('您没有权限访问该接口！', '错误')
      return;
    }
    return data
  },

  /**
   * get
   * @param url 请求地址
   * @param param 请求参数
   * @param formatFormParam 为true使用axios1表单axios服务，为false使用基础axios服务,为true会自动格式化参数
   * @param requestMethod 请求方法
   */
  async request2(url, param, formatFormParam = false, requestMethod = 'post') {
    requestMethod = requestMethod || 'post'
    param = param || {}
    let token = getToken()
    if(token != undefined) {
      token = 'Bearer ' + token;
    }
    // const token = sessionStorage.getItem('token')
    const { data } = await axios.get(url, { params: param,
      headers: {
        Accept: 'application/json, text/plain, */*',
        // 'x-session-token': '74323c60338980ff6d2d48e24d737c09',
        'Content-Type': 'application/json;charset=UTF-8',
        Authorization: token
      },
      crossDomain: true,
      withCredentials: false }
    )
    if (data.code == 207) {
      removeToken()
      this.router.push('/login')
      return
      // top.location.href = top.appCtx.publicPath + process.env.LogoutPage;
    } else if(data.code == 301) {
      MessageBox.alert('您没有权限访问该接口！', '错误')
      return;
    }
    return data
  },

  /**
   * 发送请求
   * @author
   * @date 2020-11-06 13:09
   * @param url 请求地址
   * @param param 请求参数
   * @param formatFormParam 为true使用axios1表单axios服务，为false使用基础axios服务,为true会自动格式化参数
   * @param requestMethod 请求方法
   **/
  async request(url, param, formatFormParam = false, requestMethod = 'post') {
    requestMethod = requestMethod || 'post'
    param = param || {}
    const resultParam = param
    const token = getToken()

    const res = await axios[requestMethod](url, requestMethod === 'post' ? resultParam : {
      params: JSON.stringify(resultParam)
    },
    {
      headers: {
        Accept: 'application/json, text/plain, */*',
        // 'x-session-token' :token,
        // 'x-session-token': '74323c60338980ff6d2d48e24d737c09',
        'Content-Type': 'application/json;charset=UTF-8',
        Authorization: 'Bearer ' + token
      },
      crossDomain: true,
      withCredentials: false
    }
    )

    if (res.data.code == 207) {
      removeToken()
      return
      // top.location.href = top.appCtx.publicPath + process.env.LogoutPage;
    }else if(res.data.code == 301) {
      MessageBox.alert('您没有权限访问该接口！', '错误')
      return;
    }
    return res.data
  },
  /**
   * 使用axios发送原生请求
   * @author
   * @date 2020-11-06 13:10
   **/
  async axios(...args) {
    return pureAxios(...args)
  }
}

export {
  axios,
  axios1,
  http,
  oauthHttp
}
